﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Common;
using System.Drawing;
using System.IO;
using System.Reflection;
using System.Windows.Forms;
using Xin478.CSWork.Common;
using Xin478.MySocket;

namespace Xin478.CSWork.Client
{
    public partial class TaskMainCtrl : UserControl, IMyCtrl, ICorrespondable
    { 
        public enum TabItemSelect { WorkList, FileList, CustomerList }

        TabItemSelect tabSelect=TabItemSelect.WorkList;
        IClient client;

        int currentId;

        WorkStatusFlag showMode = WorkStatusFlag.None;
        DataPageHelper dataPageHelper;
        bool clickSomeRow = false;

        public TaskMainCtrl()
        {
            InitializeComponent(); 
            this.Load += new EventHandler(TaskMainCtrl_Load);
        }

        void TaskMainCtrl_Load(object sender, EventArgs e)
        {
            this.tabControl1.SelectedTabChanging += new DevComponents.DotNetBar.TabStrip.SelectedTabChangingEventHandler(tabControl1_SelectedTabChanging);
            this.fileList.DragEnter += new DragEventHandler(fileList_DragEnter);
            this.fileList.DragDrop += new DragEventHandler(fileList_DragDrop);
            this.fileList.ItemActivate += new EventHandler(fileList_ItemActivate);
            this.taskList.ItemCheck += new ItemCheckEventHandler(taskList_ItemCheck);

            this.taskGridView.VirtualMode = true;
            this.taskGridView.EnableHeadersVisualStyles = false;
            this.taskGridView.SelectionChanged += new EventHandler(taskGridView_SelectionChanged);
            this.taskGridView.MouseDoubleClick += new MouseEventHandler(taskGridView_MouseDoubleClick);
            this.taskGridView.CellValueNeeded += new DataGridViewCellValueEventHandler(taskGridView_CellValueNeeded);
            this.taskGridView.MouseDown += new MouseEventHandler(taskGridView_MouseDown);
            this.taskGridView.RowContextMenuStripNeeded += new DataGridViewRowContextMenuStripNeededEventHandler(taskGridView_RowContextMenuStripNeeded);

            this.contextMenuStrip1.Opening += new System.ComponentModel.CancelEventHandler(contextMenuStrip1_Opening);

            dataPageHelper = new DataPageHelper(50);
            dataPageHelper.RetrieveDataInvoker = RequestData;
        }

        /// <summary>
        /// 绑定项目和事件到左侧菜单
        /// </summary>
        /// <param name="leftMenuCtrl"></param>
        public void BindLeftMenu(LeftMenuCtrl leftMenuCtrl)
        {
            if (leftMenuCtrl == null) throw new ArgumentNullException();

            MyMenuNode otherdoingNode = new MyMenuNode();
            otherdoingNode.Text = "处理中";
            otherdoingNode.MouseClick += new EventHandler(delegate(object sender, EventArgs e) { SelectThisPage(); this.ListShowMode = WorkStatusFlag.MyProcessing; });
            MyMenuNode otherFinishNode = new MyMenuNode();
            otherFinishNode.Text = "已完成";
            otherFinishNode.MouseClick += new EventHandler(delegate(object sender, EventArgs e) { SelectThisPage(); this.ListShowMode = WorkStatusFlag.MyFinished; });

            leftMenuCtrl.Nodes.Add(
                new TreeNode("接收的进程", new TreeNode[] { otherFinishNode, otherdoingNode })
            );

            MyMenuNode mywaitNode = new MyMenuNode();
            mywaitNode.Text = "等待中";
            mywaitNode.MouseClick += new EventHandler(delegate(object sender, EventArgs e) { SelectThisPage(); this.ListShowMode = WorkStatusFlag.SomeOneWaitAccept; });
            MyMenuNode mydoingNode = new MyMenuNode();
            mydoingNode.Text = "处理中";
            mydoingNode.MouseClick += new EventHandler(delegate(object sender, EventArgs e) { SelectThisPage(); this.ListShowMode = WorkStatusFlag.SomeOneProcessing; });
            MyMenuNode myFinishNode = new MyMenuNode();
            myFinishNode.Text = "已完成";
            myFinishNode.MouseClick += new EventHandler(delegate(object sender, EventArgs e) { SelectThisPage(); this.ListShowMode = WorkStatusFlag.SomeOneFinished; });

            leftMenuCtrl.Nodes.Add(
                new TreeNode("发布的进程", new TreeNode[] { myFinishNode, mydoingNode, mywaitNode })
            );

        }

        void SelectThisPage()
        {
            if (this.client.TabCtrl.SelectedIndex != 0)
                this.client.TabCtrl.SelectedIndex = 0;
        }


        /// <summary>
        /// 列表显示内容模式
        /// </summary>
        public WorkStatusFlag ListShowMode
        {
            get
            {
                return this.showMode;
            }
            set
            {
                if (this.showMode == value) return;
                this.showMode = value;
                this.dataPageHelper.Clear();
                this.taskGridView.Rows.Clear();

                this.IClient.Send("Task.任务数量", value);
                ClearInfo();
            }
        }
        
        #region 主窗体部分

        #region taskGridView操作事件

        void taskGridView_RowContextMenuStripNeeded(object sender, DataGridViewRowContextMenuStripNeededEventArgs e)
        {
            clickSomeRow = true;
            this.taskGridView.Rows[e.RowIndex].Selected = true;
        }

        void taskGridView_MouseDown(object sender, MouseEventArgs e)
        {
            clickSomeRow = false;
        }

        void taskGridView_SelectionChanged(object sender, EventArgs e)
        {
            if (this.taskGridView.SelectedRows.Count == 0) return;

            int workId = Convert.ToInt32(this.taskGridView.SelectedRows[0].Tag);
            if (workId <= 0) this.taskGridView.ClearSelection();
            else
            {
                ClearInfo();
                this.currentId = workId;
                Binds();
                if (ListSelectionChanged != null) ListSelectionChanged(this.taskGridView, workId);
            }
        }

        void taskGridView_MouseDoubleClick(object sender, MouseEventArgs e)
        {
            if (this.taskGridView.SelectedRows.Count > 0)
            {
                int id = Convert.ToInt32(this.taskGridView.SelectedRows[0].Tag);
                WorkInfo wi = Works.读取任务详细(id);
                if (wi != null) TaskForm.Instance.ShowTask(wi, this.ParentForm);
            }
        }
        #endregion

        #region 数据填充
        void RequestData(int lowerBoundary, int rowsPerPage)
        {
            this.IClient.Send("Task.任务列表", this.ListShowMode, lowerBoundary, rowsPerPage);
        }

        void taskGridView_CellValueNeeded(object sender, DataGridViewCellValueEventArgs e)
        {
            switch (e.ColumnIndex)
            {
                case 0:
                    object o = dataPageHelper.RetrieveElement(e.RowIndex, 0);
                    if (o == null) e.Value = MainFormResource.空白;
                    else
                    {
                        if (dataPageHelper.RetrieveElement(e.RowIndex, 7) != null)
                            e.Value = MainFormResource.已完成;
                        else if (dataPageHelper.RetrieveElement(e.RowIndex, 6) != null)
                            e.Value = MainFormResource.进程中;
                        else if (dataPageHelper.RetrieveElement(e.RowIndex, 6) == null)
                            e.Value = MainFormResource.待接收;
                        this.taskGridView.Rows[e.RowIndex].Tag = o;
                    }
                    break;
                case 1:
                    switch (dataPageHelper.RetrieveElement(e.RowIndex, 1))
                    {
                        case "0": e.Value = MainFormResource.最低; break;
                        case "1": e.Value = MainFormResource.普通; break;
                        case "2": e.Value = MainFormResource.较高; break;
                        default: e.Value = MainFormResource.空白; break;
                    }
                    break;
                default:
                    e.Value = dataPageHelper.RetrieveElement(e.RowIndex, e.ColumnIndex);
                    break;
            }
        }
        #endregion

        public delegate void ListSelectionChangedHandler(DataGridView view, int workId);
        public event ListSelectionChangedHandler ListSelectionChanged;

        #region 右键菜单

        void contextMenuStrip1_Opening(object sender, System.ComponentModel.CancelEventArgs e)
        {
            if (this.ListShowMode == WorkStatusFlag.SomeOneWaitAccept && this.taskGridView.SelectedRows.Count > 0 && clickSomeRow)
                右键删除菜单.Enabled = true;
            else
                右键删除菜单.Enabled = false;
        }

        void 刷新ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            this.dataPageHelper.Clear();
            this.taskGridView.Refresh();
        }

        void 删除ToolStripMenuItem_Click(object sender, EventArgs e)
        {

        }

        void 新添ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            TabPage tab=new TabPage("新建任务");
            TaskInfoCtrl ctrl=new TaskInfoCtrl();
            ctrl.IClient=this.client;
            ctrl.Dock = DockStyle.Fill;
            tab.Controls.Add(ctrl);
            this.client.TabCtrl.TabPages.Add(tab);
            this.client.TabCtrl.SelectedTab = tab;
        }

        #endregion

        #endregion

        #region IClient成员监听
        void transferFileHelper_FinishTransferHandler(TransferFileInfo transferFileInfo)
        {
            if (transferFileInfo.Status == TransferFileStatus.DownLoad)
            {
                int fid=Convert.ToInt32(transferFileInfo.Tag);
                WinForm.DoThreadSafe(this.fileList, delegate
                {
                    foreach (ListViewItem li in this.fileList.Items)
                    {
                        if (li.Tag.ToString().IndexOf(':') == -1 && fid == Convert.ToInt32(li.Tag))
                        {
                            li.ForeColor = Color.Black;
                            break;
                        }
                    }
                });
                OpenFile(UserSession.Current.ReceiveFilePath + transferFileInfo.ToFileName);
                
            }
        }

        void CommandReceive(DatagramBuilder builder, ref bool cancel)
        {
            MethodInfo mi = typeof(TaskMainCtrl).GetMethod(builder.Name, BindingFlags.NonPublic | BindingFlags.IgnoreCase | BindingFlags.Instance);
            if (mi != null)
            {
                mi.Invoke(this, builder.Params);
                cancel = true;
            }
        }
        #endregion

        #region 下部标签部分

        #region 标签文件列表
        void fileList_ItemActivate(object sender, EventArgs e)
        {
            ListViewItem li = fileList.FocusedItem;
            string filePath=null;
            if (li.Tag.ToString().IndexOf(':') == -1)
            {/*
                if (this.workInfo.WorkFileInfos == null) return;
                int fid = Convert.ToInt32(li.Tag);

                foreach (WorkFileInfo fileInfo in this.workInfo.WorkFileInfos)
                {
                    if (fileInfo.Id == fid)
                    {
                        if (!File.Exists(UserSession.Current.ReceiveFilePath + fileInfo.FileCode + fileInfo.FileExt))
                            ((MainForm)ParentForm).Send("Task.文件下载", fid);
                        else
                            filePath=UserSession.Current.ReceiveFilePath + fileInfo.FileCode + fileInfo.FileExt;
                        break;
                    }
                }*/
            }
            else
            {
                filePath = li.Tag.ToString();
            }
            
            OpenFile(filePath);
        }
        void OpenFile(string filePath)
        {
            if (string.IsNullOrEmpty(filePath) || !File.Exists(filePath)) return;
            try
            {
                System.Diagnostics.Process.Start(filePath);
            }
            catch { return; }
        }
        void fileList_DragEnter(object sender, DragEventArgs e)
        {
            if (e.Data.GetDataPresent(DataFormats.FileDrop))
            {
                e.Effect = DragDropEffects.Copy;
            }
            else
            {
                e.Effect = DragDropEffects.None;
            }
        }
        void fileList_DragDrop(object sender, DragEventArgs e)
        {
            String[] files;
            files = e.Data.GetData(DataFormats.FileDrop, false) as String[];

            ListViewGroup groupNow;
            string groupname=DateTime.Now.ToString("yyyy-MM-dd");
            if (fileList.Groups.Count == 0)
            {
                groupNow = new ListViewGroup();
                groupNow.Header = groupname;
                fileList.Groups.Add(groupNow);
            }
            else 
            {
                if (fileList.Groups[0].Header.Equals(groupname))
                    groupNow = fileList.Groups[0];
                else
                {
                    groupNow = new ListViewGroup();
                    groupNow.Header = groupname;
                    fileList.Groups.Insert(0,groupNow);
                }
            }
            foreach (string file in files)
            {
                if (File.Exists(file))
                {
                    Icon ico= IcoHelper.GetFileIcon(file, true);
                    fileIcoList.Images.Add(ico);
                    ListViewItem item=new ListViewItem();
                    item.ImageIndex=fileIcoList.Images.Count-1;
                    item.Tag = file;
                    item.ForeColor=Color.Blue;
                    item.Text=file.Substring(file.LastIndexOf('\\')+1);
                    item.Group = groupNow;
                    fileList.Items.Add(item);
                }
                else if (Directory.Exists(file))
                {
                }
            }
        }
        #endregion

        #region 标签任务列表部分
        void taskList_ItemCheck(object sender, ItemCheckEventArgs e)
        {
            bool flag = false;
            throw new ArgumentNullException();
            /*
            if (this.workInfo != null
                && this.workInfo.FinishTime == null
                && this.workInfo.UserId == UserSession.Current.EmployeeInfo.Id
                && this.workInfo.WorkCommandInfos != null)
            {
                int cid = Convert.ToInt32(this.taskList.Items[e.Index].Tag);
                List<WorkCommandInfo> cmds = (List<WorkCommandInfo>)this.workInfo.WorkCommandInfos;
                WorkCommandInfo cmd = cmds.Find(delegate(WorkCommandInfo c) { return c.Id == cid; });
                if (cmd != null && cmd.FinishTime == null)
                {
                    flag = true;
                }
                else
                    flag = e.CurrentValue == CheckState.Checked;
            }
            else
                flag = e.CurrentValue == CheckState.Checked;
            */
            e.NewValue = flag ? CheckState.Checked : CheckState.Unchecked;
        }
        #endregion

        void tabControl1_SelectedTabChanging(object sender, DevComponents.DotNetBar.TabStripTabChangingEventArgs e)
        {
            switch (e.NewTab.Name)
            {
                case "tabItem5":
                    this.TabItemSelected = TabItemSelect.CustomerList;
                    break;
                case "tabItem4":
                    this.TabItemSelected = TabItemSelect.WorkList;
                    break;
                case "tabItem3":
                    this.TabItemSelected = TabItemSelect.FileList;
                    break;
            }
        }
        public TabItemSelect TabItemSelected
        {
            get
            {
                return this.tabSelect;
            }
            set
            {
                if (this.tabSelect != value)
                {
                    Binds();
                }
            }
        }
        void Binds()
        {
            switch (TabItemSelected)
            {
                case TabItemSelect.WorkList:
                    BindWorkList();
                    break;
                case TabItemSelect.FileList:
                    BindFileList();
                    break;
                case TabItemSelect.CustomerList:
                    break;
            }
        }
        void ClearInfo()
        {
            taskList.Items.Clear();
            fileList.Items.Clear();
            fileIcoList.Images.Clear();
        }

        void BindWorkList()
        {
            if (this.tabSelect != TabItemSelect.WorkList) return;

            this.taskList.Items.Clear();
            this.client.Send("任务要求列表", this.currentId);
        }
        void BindWorkList(IList<WorkCommandInfo> cmds)
        {
            if (cmds == null) return;

            foreach (WorkCommandInfo cmd in cmds)
            {
                ListViewItem item = new ListViewItem();
                item.Tag = cmd.Id.ToString();
                item.Checked = cmd.IsFinished;
                item.SubItems.AddRange(new string[] { cmd.Request,cmd.LatestTime.ToString(),cmd.FinishTime.ToString()});
                this.taskList.Items.Add(item);
            }
        }
        void BindFileList()
        {
            if (this.tabSelect != TabItemSelect.FileList) return;

            this.fileList.Items.Clear();
            this.fileList.Groups.Clear();
            this.fileIcoList.Images.Clear();
            this.client.Send("任务文件列表", this.currentId);
        }
        void BindFileList(IList<WorkFileInfo> workFileInfos)
        {
            if (workFileInfos == null) return;

            ListViewGroup lgroup=null;
            foreach (WorkFileInfo wf in workFileInfos)
            {
                ListViewItem item=new ListViewItem();
                item.Text=wf.FileName;
                item.Tag = wf.Id;
                Icon ico= IcoHelper.GetFileIcon(wf.FileName, true);
                fileIcoList.Images.Add(ico);
                item.ImageIndex = fileIcoList.Images.Count - 1;
                if (!File.Exists(UserSession.Current.ReceiveFilePath + wf.FileCode + wf.FileExt)) item.ForeColor = Color.DarkGray;
                
                string group =  wf.AddTime.Value.ToString("yyyy-MM-dd");
                if (lgroup == null || !lgroup.Header.Equals(group))
                {
                    lgroup = new ListViewGroup();
                    lgroup.Header = group;
                    this.fileList.Groups.Add(lgroup);
                }
                item.Group = lgroup;
                this.fileList.Items.Add(item);
            }
        }

        #endregion

        #region 回调
        void 任务数量(NetEventArgs e, int count, WorkStatusFlag status)
        {
            if (this.showMode == status)
            {
                WinForm.DoThreadSafe(this.taskGridView, delegate() { 
                    this.taskGridView.Rows.Clear(); 
                    this.taskGridView.RowCount = count;

                    ClearInfo();
                });
            }
        }
        void 任务列表(NetEventArgs e,int rowIndex, DataTable table)
        {
            dataPageHelper.FillPage(rowIndex, table);
            WinForm.DoThreadSafe(this.taskGridView, delegate() { this.taskGridView.Refresh(); });
        }
        void 任务当前(NetEventArgs e, IList<WorkInfo> works)
        {
            if (works != null)
            {                
                bool flag=true;
                int count = 0;

                foreach (WorkInfo wi in works)
                {
                    if (Db.MyWork.Select(MyWork.Works, MyWork.Works.Id).Where(MyWork.Works.Id == wi.Id).ToScalar() != null) continue;

                    DbTransaction tran = Db.MyWork.BeginTransaction();

                    wi.AcceptTime = DateTime.Now;
                    if (Db.MyWork.Insert(MyWork.Works)
                        .AddColumn(MyWork.Works.Id, wi.Id)
                        .AddColumn(MyWork.Works.Title, wi.Title)
                        .AddColumn(MyWork.Works.AddTime, wi.AddTime)
                        .AddColumn(MyWork.Works.AcceptTime, wi.AcceptTime)
                        .AddColumn(MyWork.Works.LatestTime, wi.LatestTime)
                        .AddColumn(MyWork.Works.FinishTime, wi.FinishTime)
                        .AddColumn(MyWork.Works.UserId, wi.UserId)
                        .AddColumn(MyWork.Works.Weight, wi.Weight)
                        .AddColumn(MyWork.Works.PublisherId, wi.PublisherId)
                        .AddColumn(MyWork.Works.IsFinished, wi.IsFinished)
                        .SetTransaction(tran)
                        .Execute() != 1)
                    {
                        tran.Rollback();
                        continue;
                    }

                    if (wi.WorkCommandInfos != null)
                    {
                        foreach (WorkCommandInfo cmd in wi.WorkCommandInfos)
                        {
                            if (Db.MyWork.Insert(MyWork.WorkCommands)
                                .AddColumn(MyWork.WorkCommands.Id, cmd.Id)
                                .AddColumn(MyWork.WorkCommands.WorkId, cmd.WorkId)
                                .AddColumn(MyWork.WorkCommands.Request, cmd.Request)
                                .AddColumn(MyWork.WorkCommands.IsFinished, cmd.IsFinished)
                                .AddColumn(MyWork.WorkCommands.LatestTime, cmd.LatestTime)
                                .AddColumn(MyWork.WorkCommands.FinishTime, cmd.FinishTime)
                                .AddColumn(MyWork.WorkCommands.Weight, cmd.Weight)
                                .SetTransaction(tran)
                                .Execute() != 1)
                            {
                                flag = false;
                                break;
                            }
                        }

                        if (!flag)
                        {
                            tran.Rollback();
                            continue;
                        }
                    }

                    if (wi.WorkFileInfos != null)
                    {
                        foreach (WorkFileInfo fi in wi.WorkFileInfos)
                        {
                            if (Db.MyWork.Insert(MyWork.WorkFiles)
                                   .AddColumn(MyWork.WorkFiles.Id, fi.Id)
                                   .AddColumn(MyWork.WorkFiles.FileName, fi.FileName)
                                   .SetTransaction(tran)
                                   .Execute() != 1)
                            {
                                flag = false;
                                break;
                            }
                        }

                        if (!flag)
                        {
                            tran.Rollback();
                            continue;
                        }
                    }

                    tran.Commit();
                    count++;
                    client.Send("接受任务", wi.Id, wi.AcceptTime);
                }

                //if(count>0)  mainForm.弹出提示(10000, "有新任务", "您有" + count.ToString() + "条新任务");

                client.Send("任务当前", works[works.Count - 1].Id);
            }

        }

        void 任务信息(NetEventArgs e, WorkInfo wi)
        {
            if (wi == null) return;
/*
            WinForm.DoThreadSafe(this, delegate() 
            {
                if (workInfo == null)
                {
                    workInfo = wi;
                }
                else if (wi.Id == workInfo.Id)
                {
                    WorkInfo _wi = workInfo;
                    workInfo = wi;
                    if (_wi.WorkCommandInfos != null) workInfo.WorkCommandInfos = _wi.WorkCommandInfos;
                    if (_wi.WorkFileInfos != null) workInfo.WorkFileInfos = _wi.WorkFileInfos;
                    if (_wi.CustomerInfo != null) workInfo.CustomerInfo = _wi.CustomerInfo;
                }
                else
                    return;

                BindWorkInfo();
            });*/
        }
        void 任务要求列表(NetEventArgs e,int workId, IList<WorkCommandInfo> cmds)
        {/*
            WinForm.DoThreadSafe(this, delegate()
               {
                   if (workInfo == null)
                   {
                       workInfo = new WorkInfo();
                       workInfo.Id = workId;
                   }

                   if (workId == this.workInfo.Id)
                   {
                       this.workInfo.WorkCommandInfos = cmds;
                       BindWorkList(cmds);
                   }
               });*/
        }
        void 任务文件列表(NetEventArgs e, int workId, IList<WorkFileInfo> wfiles)
        {/*
            WinForm.DoThreadSafe(this, delegate() 
            {
                if (workInfo == null)
                {
                    workInfo = new WorkInfo();
                    workInfo.Id = workId;
                }

                if (workId == this.workInfo.Id)
                {
                    this.workInfo.WorkFileInfos = wfiles;
                    BindFileList(wfiles);
                }
            });
          * */
        }        
        #endregion

        #region ICorrespondable 成员

        public IClient IClient
        {
            set {
                if (value == null) throw new ArgumentNullException();

                this.client = value;
                client.CommandReceived += CommandReceive;
                client.TransferFileHelper.FinishTransferHandler += new TransferFileHelper.TransferHandler(transferFileHelper_FinishTransferHandler);
            }
            get { return client; }
        }
        #endregion

        #region IMyCtrl 成员

        public void Sleep()
        {
            this.taskGridView.Rows.Clear();
            ClearInfo();
        }

        public void WakeUp()
        {
        }

        public UnsetMethod UnsetMethod
        {
            get { return UnsetMethod.OnlyHide; }
        }

        #endregion
    }
}
